package com.example.kingdee.block;

import cn.hutool.core.date.DateUtil;
import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONArray;
import com.alibaba.fastjson2.JSONObject;
import com.example.kingdee.KingdeeCreate.dto.CreateInDto;
import com.example.kingdee.KingdeeCreate.impl.CreateSalBillImpl;
import com.example.kingdee.common.StringUtils;
import com.example.kingdee.common.constant.YiTiConstant;
import com.example.kingdee.config.RuoYiConfig;
import com.example.kingdee.dto.PurchaseSyncDto;
import com.example.kingdee.entity.*;
import com.example.kingdee.exception.ProcedureException;
import com.example.kingdee.kingdeeBridge.common.RequestResult;
import com.example.kingdee.mapper.TBxStMapper;
import com.example.kingdee.sqlTool.SqlTool;
import com.example.kingdee.sqlTool.sqltoolEnum.FormIdEnum;
import com.example.kingdee.util.JuShuiTanUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.io.IOException;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;

@Service
public class JuShuiTanBlock {

    @Autowired
    private TBxStMapper tBxStMapper;

    @Autowired
    private RuoYiConfig ruoYiConfig;

    @Autowired
    private CreateSalBillImpl createSalBill;

    private static Logger logger = LoggerFactory.getLogger(JuShuiTanBlock.class);


    /**
     * Function：获取AccessToken
     *
     * @author Wangyx
     * @date 2021/12/31 15:33
     * @version 1.0.0
     */
    public String getAccessToken(){
        //先从数据库中获取accessToken
        AccessTokenDO accessTokenDo = tBxStMapper.getAccessToken(YiTiConstant.mark);
        if (accessTokenDo != null){
            //获取过期时间
            Date expirationTime = accessTokenDo.getExpirationTime();
            //获取当前时间
            Date date = new Date();
            if (date.before(expirationTime)){
                //未过期则直接返回accessToken
                return accessTokenDo.getAccessToken();
            }else {
                //若过期了则刷新accessToken
                String accessTokenJson = JuShuiTanUtil.refreshToken(accessTokenDo.getRefreshToken());
                JSONObject jsonObject = JSON.parseObject(accessTokenJson);
                String statusCode = jsonObject.getString("code");
                if ("0".equals(statusCode)) {
                    return disposeAccessTokenJson(jsonObject);
                } else {
                    logger.error(SqlTool.modifyItemSyncLogInfo(new ArrayList<>(), YiTiConstant.JST_ACCESSTOKEN_ERROR, "失败", jsonObject.get("msg").toString()));
                    throw new ProcedureException("更新accessToken失败");
                }
            }
        }
        //若数据库中不存在accessToken，获取AccessToken
        String accessTokenJson = JuShuiTanUtil.getAccessToken(getLinkNo());
        JSONObject jsonObject = JSON.parseObject(accessTokenJson);
        String statusCode = jsonObject.getString("code");
        if ("0".equals(statusCode)) {
            return disposeAccessTokenJson(jsonObject);
        } else {
            logger.error(SqlTool.modifyItemSyncLogInfo(new ArrayList<>(), YiTiConstant.JST_ACCESSTOKEN_ERROR, "失败", jsonObject.get("msg").toString()));
            throw new ProcedureException("获取accessToken失败");
        }
    }

    public String disposeAccessTokenJson(JSONObject jsonObject){
        String data = jsonObject.getString("data");

        tBxStMapper.deleteAccessToken(YiTiConstant.mark);

        AccessTokenDO accessToken = JSON.parseObject(data, AccessTokenDO.class);
        //1.保存到数据库，
        accessToken.setMark(YiTiConstant.mark);
        Long expirationTime = System.currentTimeMillis() / 1000 + Long.valueOf(accessToken.getExpiresIn()) - 3600;
        //过期时间设置提前设置1小时
        Date date = new Date(expirationTime * 1000);
        accessToken.setExpirationTime(date);
        tBxStMapper.saveAccessToken(accessToken);
        return accessToken.getAccessToken();
    }

    public String getLinkNo() {
        String linkNo = "";
        // 用字符数组的方式随机
        String model = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
        char[] m = model.toCharArray();
        for (int j = 0; j < 6; j++) {
            char c = m[(int) (Math.random() * 36)];
            // 保证六位随机数之间没有重复的
            if (linkNo.contains(String.valueOf(c))) {
                j--;
                continue;
            }
            linkNo = linkNo + c;
        }
        return linkNo;
    }


    /**
     * 查询采购订单
     *
     * @return
     * @throws IOException
     */
    public String getJstInfo(PurchaseSyncDto purchaseSyncDto) {
        HashMap<String, Object> params = new HashMap<>();
        //指定单据状态
        params.put("statuss", purchaseSyncDto.getStatusList());
        //指定查询起始页
        params.put("page_index", purchaseSyncDto.getIndex() == null ? 1 : purchaseSyncDto.getIndex());
        //指定每页查询的数据量
        params.put("page_size", purchaseSyncDto.getPageSize() == null ? 50 : purchaseSyncDto.getPageSize());
        //制定查询采购单号
        if (purchaseSyncDto.getPoIds() != null && purchaseSyncDto.getPoIds().size() != 0){
            params.put("po_ids", purchaseSyncDto.getPoIds());
        }
        //指定查询开始结束时间
        if (!StringUtils.isEmpty(purchaseSyncDto.getStarTimeStr()) && !StringUtils.isEmpty(purchaseSyncDto.getEndTimeStr())){
            params.put("modified_begin", purchaseSyncDto.getStarTimeStr());
            params.put("modified_end", purchaseSyncDto.getEndTimeStr());
        }
        String url = ruoYiConfig.getOpenApiUrl() + FormIdEnum.getDBTableName(purchaseSyncDto.getJstFormId());
        return JuShuiTanUtil.sendQueryHttp(url, params, getAccessToken());
    }

    /**
     * 查询销售订单
     *
     * @return
     * @throws IOException
     */
    public String getJstSalInfo(PurchaseSyncDto purchaseSyncDto) {
        HashMap<String, Object> params = new HashMap<>();
        //指定单据状态
        params.put("status", purchaseSyncDto.getStatusList().get(0));
        //指定查询起始页
        params.put("page_index", purchaseSyncDto.getIndex() == null ? 1 : purchaseSyncDto.getIndex());
        //指定每页查询的数据量
        params.put("page_size", purchaseSyncDto.getPageSize() == null ? 50 : purchaseSyncDto.getPageSize());
        //制定查询采购单号
        if (purchaseSyncDto.getPoIds() != null && purchaseSyncDto.getPoIds().size() != 0){
            params.put("o_ids", purchaseSyncDto.getPoIds());
        }
        //指定查询开始结束时间
        if (!StringUtils.isEmpty(purchaseSyncDto.getStarTimeStr()) && !StringUtils.isEmpty(purchaseSyncDto.getEndTimeStr())){
            params.put("modified_begin", purchaseSyncDto.getStarTimeStr());
            params.put("modified_end", purchaseSyncDto.getEndTimeStr());
        }
        String url = ruoYiConfig.getOpenApiUrl() + FormIdEnum.getDBTableName(purchaseSyncDto.getJstFormId());
        return JuShuiTanUtil.sendSalQueryHttp(url, params, getAccessToken());
    }

    /**
     * 查询售后订单
     *
     * @return
     * @throws IOException
     */
    public String getJstReFundInfo(PurchaseSyncDto purchaseSyncDto) {
        HashMap<String, Object> params = new HashMap<>();
        //指定单据状态
        params.put("status", purchaseSyncDto.getStatusList().get(0));
        //指定查询起始页
        params.put("page_index", purchaseSyncDto.getIndex() == null ? 1 : purchaseSyncDto.getIndex());
        //指定每页查询的数据量
        params.put("page_size", purchaseSyncDto.getPageSize() == null ? 50 : purchaseSyncDto.getPageSize());
        //制定查询采购单号
        if (purchaseSyncDto.getPoIds() != null && purchaseSyncDto.getPoIds().size() != 0){
            params.put("as_ids", purchaseSyncDto.getPoIds());
        }
        //指定查询开始结束时间
        if (!StringUtils.isEmpty(purchaseSyncDto.getStarTimeStr()) && !StringUtils.isEmpty(purchaseSyncDto.getEndTimeStr())){
            params.put("modified_begin", purchaseSyncDto.getStarTimeStr());
            params.put("modified_end", purchaseSyncDto.getEndTimeStr());
        }
        String url = ruoYiConfig.getOpenApiUrl() + FormIdEnum.getDBTableName(purchaseSyncDto.getJstFormId());
        return JuShuiTanUtil.sendQueryHttp(url, params, getAccessToken());
    }

    /**
     * 查询仓库
     *
     * @return
     * @throws IOException
     */
    public String getStock() {
        HashMap<String, Object> params = new HashMap<>();
        //指定单据状态
        params.put("page_size", 100);
        String url = ruoYiConfig.getOpenApiUrl() + "/open/wms/partner/query";
        return JuShuiTanUtil.getStockInfo(url, params, getAccessToken());
    }

    /**
     * 查询快递公司
     *
     * @return
     * @throws IOException
     */
    public String getEmp() {
        HashMap<String, Object> params = new HashMap<>();
        //指定单据状态
        params.put("page_size", 50);
        String url = ruoYiConfig.getOpenApiUrl() + "/open/logisticscompany/query";
        return JuShuiTanUtil.getStockInfo(url, params, getAccessToken());
    }



    //同步采购订单
    public void savaPurchase(List<JstPurchase> jstPurchaseList, String endConfirmDate) {
        for (JstPurchase jstPurchase : jstPurchaseList) {
            if (!StringUtils.isEmpty(jstPurchase.getPoDate())){
                boolean before = true;
                if (!StringUtils.isEmpty(endConfirmDate)){
                    //判断审核截止日期
                    Date poDate = DateUtil.parse(jstPurchase.getPoDate());
                    Date comparePoDate = DateUtil.parse(endConfirmDate);
                    before = comparePoDate.before(poDate);
                }
                //判断单号是否存在
                int isExist = tBxStMapper.salOrderIsExist(String.valueOf(jstPurchase.getPoId()));
                if (isExist == 0 && before && jstPurchase.getStatus().equals("Confirmed")){
                    //构建数据
                    CreateInDto createInDto = new CreateInDto();
                    createInDto.setReserved1(jstPurchase.getPoId());
                    createInDto.setReserved2(jstPurchase.getPoDate());
                    createInDto.setReserved3(jstPurchase.getRemark());
                    createInDto.setReserved4(jstPurchase.getPoId());
                    createInDto.setReserved5(jstPurchase.getConfirmDate());
                    createInDto.setReserved6(jstPurchase.getWmsCoId());
                    createInDto.setItems(jstPurchase.getItems());
                    //创建销售订单
                    RequestResult result = createSalBill.createSrcBill(createInDto);
                    //审核销售订单
                    createSalBill.auditTargetBill(result.getNumber());
                    if (result.getCode().equals("200")){
                        //保存同步成功日志
                        SyncLog syncLog = new SyncLog("采购订单同步", String.valueOf(jstPurchase.getPoId()),"聚水潭采购单", "金蝶销售单", result.getNumber(),
                                SqlTool.getNowForString(), "系统自动同步", "同步成功", "同步成功");
                        insertSyncLog(syncLog);
                    }else {
                        //保存同步成功日志
                        SyncLog syncLog = new SyncLog("采购订单同步", String.valueOf(jstPurchase.getPoId()), "聚水潭采购单","金蝶销售单", "",
                                SqlTool.getNowForString(), "系统自动同步", "同步失败", result.getMsg());
                        insertSyncLog(syncLog);
                    }
                }
            }
        }
    }

    public void insertSyncLog(SyncLog syncLog){
        tBxStMapper.insertSyncLog(syncLog);
    }

}
